package com.gc.web.controller.api;

import cn.hutool.core.date.DateUtil;
import cn.hutool.core.util.NumberUtil;
import com.alibaba.fastjson.JSONObject;
import com.gc.business.domain.*;
import com.gc.business.service.*;
import com.gc.common.constant.Constants;
import com.gc.common.support.Convert;
import com.gc.common.utils.DateUtils;
import com.gc.common.utils.StringUtils;
import com.gc.framework.web.base.ApiBaseController;
import com.gc.system.domain.SysUser;
import com.gc.system.service.ISysUserService;
import com.github.pagehelper.PageInfo;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Controller;
import org.springframework.transaction.annotation.Transactional;
import org.springframework.web.bind.annotation.*;

import java.util.ArrayList;
import java.util.HashMap;
import java.util.List;
import java.util.Map;

/**
 * @title 电梯保养相关api接口层
 * @Date 2020/11/20 17:00
 * @author hruiyan
 */
@CrossOrigin
@Controller
@RequestMapping("/api/upkeep")
public class ApiUpkeepInfoController extends ApiBaseController {

    /**
     * 保养主信息
     */
    @Autowired
    private IUpkeepInfoService upkeepInfoService;

    /**
     * 保养记录
     */
    @Autowired
    private IUpkeepRecordService upkeepRecordService;

    /**
     * 保养计划
     */
    @Autowired
    private IUpkeepPlanService upkeepPlanService;

    /**
     * 保养项目清单
     */
    @Autowired
    private IUpkeepProjectService upkeepProjectService;

    /**
     * 保养项目清单记录
     */
    @Autowired
    private IUpkeepProjectRecordService upkeepProjectRecordService;

    @Autowired
    private ISysUserService userService;

    @Autowired
    private IIntegralConfigService integralConfigService;

    @Autowired
    private IIntegralDetailService integralDetailService;


    /**
     * 我的保养-列表接口(保养过的记录)
     * @param token
     * @param pageNum
     * @param pageSize
     * @return
     */
    @GetMapping("/selectMineUpkeepList")
    @ResponseBody
    public Map<String,Object> selectMineUpkeepList(String token,Integer pageNum,Integer pageSize){
        Long userId = getUserId(token);
        //查询我的保养记录列表
        startPage(pageNum,pageSize,"i.create_time DESC");
        List<UpkeepInfo> upkeepList = upkeepInfoService.selectListByReviewUserId(userId, null);

        //返回前端数据处理
        List<Map<String,Object>> mapList = new ArrayList<>();
        Map<String,Object> map = null;
        for (UpkeepInfo upkeepInfo : upkeepList) {
            map = new HashMap<>();
            map.put("upkeepId",upkeepInfo.getUpkeepId());
            //电梯名称
            map.put("elevatorName",upkeepInfo.getElevatorName());
            //电梯类型 1.直梯 2.扶梯
            map.put("elevatorType",upkeepInfo.getUpkeepTemplate().getElevatorType());
            //保养类型
            map.put("upkeepType",upkeepInfo.getUpkeepType());
            //保养状态(1.正常，2.超期)3. 通过
            map.put("upkeepState",upkeepInfo.getUpkeepState());
            //审核人
            map.put("auditUser",upkeepInfo.getAuditUser());
            //确认时间
            map.put("confirmDate", upkeepInfo.getAuditTime());
            //包养人
            map.put("referUser",upkeepInfo.getReferUser());

            mapList.add(map);
        }
        Map<String,Object> mapReturn = new HashMap<>();
        mapReturn.put("pageNum",pageNum);
        mapReturn.put("list",mapList);
        mapReturn.put("total", new PageInfo<>(mapList).getTotal());
        return success(mapReturn);
    }


    /**
     * 保养记录 -电梯的保养记录
     * @param elevatorId
     * @param pageNum
     * @param pageSize
     * @return
     */
    @GetMapping("/selectElevatorUpkeepList")
    @ResponseBody
    public Map<String,Object> selectElevatorUpkeepList(Long elevatorId,Integer pageNum,Integer pageSize){

        if(StringUtils.isNull(elevatorId)){
            return error(Constants.UNVERIFY,"缺少必要参数：elevatorId");
        }

        startPage(pageNum,pageSize,"i.create_time DESC");
        List<UpkeepInfo> upkeepList = upkeepInfoService.selectListByReviewType(new UpkeepInfo() {{
            setElevatorId(elevatorId);
        }}, null,null);

        //返回前端数据处理
        List<Map<String,Object>> mapList = new ArrayList<>();
        Map<String,Object> map = null;
        for (UpkeepInfo upkeepInfo : upkeepList) {
            map = new HashMap<>();
            map.put("upkeepId",upkeepInfo.getUpkeepId());
            //电梯名称
            map.put("elevatorName",upkeepInfo.getElevatorName());
            //保养类型
            map.put("upkeepType",upkeepInfo.getUpkeepType());
            //维保人员
            Long[] applicantIds = Convert.toLongArray(upkeepInfo.getApplicant());
            String applicantUser = "";
            for (Long applicantId : applicantIds) {
                SysUser user = userService.selectUserById(applicantId);
                if (user == null){continue;}
                applicantUser = user.getUserName() + ",";
            }
            map.put("referUserArray",applicantUser);
            //审核人
            map.put("auditUser",upkeepInfo.getAuditUser());
            //确认时间
            map.put("confirmDate", upkeepInfo.getAuditTime());
            //保养状态(1.正常，2.超期)3. 通过
            map.put("upkeepState",upkeepInfo.getUpkeepState());

            mapList.add(map);
        }
        Map<String,Object> mapReturn = new HashMap<>();
        mapReturn.put("pageNum",pageNum);
        mapReturn.put("list",mapList);
        mapReturn.put("total", new PageInfo<>(mapList).getTotal());
        return success(mapReturn);
    }


    /**
     * 开始保养接口: 返回详情信息
     * @param upkeepId
     * @return
     */
    @PostMapping("/startUpkeep")
    @ResponseBody
    @Transactional(rollbackFor = Exception.class)
    public Map<String,Object> startUpkeep(Long upkeepId,String token){
        if(StringUtils.isNull(upkeepId)){
            return error(Constants.UNVERIFY,"缺少必要参数");
        }
        UpkeepInfo byId = upkeepInfoService.selectAllInfoById(upkeepId);
        if(StringUtils.isNull(byId)){
            return error(Constants.UNVERIFY,"参数有误");
        }

        if(byId.getUpkeepRecordList().size() > 0 && StringUtils.isNotNull(byId.getUpkeepRecordList())
            && StringUtils.isNotNull(byId.getUpkeepRecordList().get(0).getReferUserId())){
            if(!byId.getUpkeepRecordList().get(0).getReferUserId().equals(getUserId(token))){
                return error(Constants.UNVERIFY,"该保养已被其他工程师接取！");
            }
        }else{
            SysUser sysUser = userService.selectUserById(getUserId(token));
            byId.setAvatar(sysUser.getAvatar()); //开始人头像
            byId.setStartTime(DateUtil.date());
            upkeepInfoService.updateById(byId);

            //添加保养记录
            UpkeepRecord upkeepRecord = new UpkeepRecord();
            upkeepRecord.setUpkeepId(byId.getUpkeepId());
            upkeepRecord.setReferUserId(getUserId(token));
            upkeepRecord.setCreateTime(DateUtil.date());
            upkeepRecordService.save(upkeepRecord);
        }
        //返回电梯类型
        JSONObject jsonObject = new JSONObject();
        jsonObject.put("elevatorType",byId.getUpkeepTemplate().getElevatorType());
        return success(jsonObject);
    }


    /**
     * 查询工作-保养列表数据接口
     * @param token
     * @param reviewType 0.待保养 1.待确认 2.已通过
     * @return
     */
    @GetMapping("/selectUpkeepAuditList")
    @ResponseBody
    public Map<String,Object> selectUpkeepAuditList(String token,Integer reviewType,Integer pageNum,Integer pageSize){
        String userId = String.valueOf(getUserId(token));
        startPage(pageNum,pageSize,"i.create_time DESC");
        List<UpkeepInfo> upkeepList = upkeepInfoService.selectListByReviewType(new UpkeepInfo() {{
            setApplicant(userId);
        }}, reviewType,null);


        //返回前端数据处理
        List<Map<String,Object>> mapList = new ArrayList<>();
        Map<String,Object> map = null;
        for (UpkeepInfo upkeepInfo : upkeepList) {
            map = new HashMap<>();
            map.put("upkeepId",upkeepInfo.getUpkeepId());
            //电梯名称
            map.put("elevatorName",upkeepInfo.getElevatorName());
            //保养类型
            map.put("upkeepType",upkeepInfo.getUpkeepType());
            //截止时间
            map.put("overTime", DateUtils.getISO8601Timestamp(upkeepInfo.getOverTime()));
            //保养人
            map.put("referUser",upkeepInfo.getReferUser());
            //维保人员
            Long[] applicantIds = Convert.toLongArray(upkeepInfo.getApplicant());
            String applicantUser = "";
            for (Long applicantId : applicantIds) {
                SysUser user = userService.selectUserById(applicantId);
                if(StringUtils.isNotNull(user)){
                    applicantUser = user.getUserName() + ",";
                }
            }
            map.put("referUserArray",applicantUser);

            //审核人
            map.put("auditUser",upkeepInfo.getAuditUser());
            //确认时间
            map.put("confirmDate", upkeepInfo.getAuditTime());
            //保养状态(1.正常，2.超期)3. 通过
            map.put("upkeepState",upkeepInfo.getUpkeepState());

            mapList.add(map);
        }
        Map<String,Object> mapReturn = new HashMap<>();

        mapReturn.put("pageNum",pageNum);
        mapReturn.put("list",mapList);
        mapReturn.put("total", new PageInfo<>(mapList).getTotal());
        return success(mapReturn);
    }


    /**
     * 查询列表类型数量接口
     * @param token
     * @return
     */
    @GetMapping("/selectAllListNum")
    @ResponseBody
    public Map<String,Object> selectAllListNum(String token){

        String userId = String.valueOf(getUserId(token));

        List<JSONObject> jsonObjectList = new ArrayList<>();

        JSONObject jSONObject = null;
        for(int i=0;i<3;i++){
            //返回各个状态下数据数量
            startPage(null,null,"i.create_time DESC");
            List<UpkeepInfo> upkeepList = upkeepInfoService.selectListByReviewType(new UpkeepInfo() {{
                setApplicant(userId);
            }}, i,null);

            jSONObject = new JSONObject();
            if(i == 0){
                jSONObject.put("title","待保养");
            }else if(i == 1){
                jSONObject.put("title","待确认");
            }else if(i == 2){
                jSONObject.put("title","已通过");
            }
            jSONObject.put("num",new PageInfo<>(upkeepList).getTotal());
            jsonObjectList.add(jSONObject);
        }
        return success(jsonObjectList);
    }

    /**
     * 进行保养项目清单页面详情接口
     * @param upkeepId
     * @return
     */
    @PostMapping("/selectUpkeepProjectDetails")
    @ResponseBody
    @Transactional(rollbackFor = Exception.class)
    public Map<String,Object> selectUpkeepProjectDetails(Long upkeepId,String projectType){
        if(StringUtils.isNull(upkeepId)){
            return error(Constants.UNVERIFY,"缺少必要参数");
        }
        UpkeepInfo byId = upkeepInfoService.selectAllInfoById(upkeepId);
        if(StringUtils.isNull(byId)){
            return error(Constants.UNVERIFY,"参数有误");
        }

        Map<String,Object> map = new HashMap<>();
        //电梯种类 1.直梯 2.扶梯
        map.put("elevatorType",byId.getUpkeepTemplate().getElevatorType());
        //保养,电梯信息
        map.put("upkeepInfo",byId);

        //查询是否保存过项目保养记录
        List<UpkeepProjectRecord> projectRecordList = upkeepProjectRecordService.list(new UpkeepProjectRecord() {{
            setUpkeepId(upkeepId);
            setProjectType(byId.getUpkeepTemplate().getElevatorType().equals("2") ? "0" :   //如果为扶梯
                    projectType == null ? "1" : projectType
            );
        }});

        //查询模板是否含有
        List<UpkeepProject> upkeepProjectList = upkeepProjectService.list(new UpkeepProject() {{
            setTemplateId(byId.getTemplateId());
            setProjectType(byId.getUpkeepTemplate().getElevatorType().equals("2") ? "0" :   //如果为扶梯
                    projectType == null ? "1" : projectType
            );
        }});

        if(projectRecordList.size() > 0){}else if(upkeepProjectList.size() >0){
            //没有则保存一遍
            for (UpkeepProject upkeepProject : upkeepProjectList) {
                UpkeepProjectRecord upkeepProjectRecord = new UpkeepProjectRecord(upkeepId,upkeepProject.getProjectName(),upkeepProject.getProjectRequire(),"2",upkeepProject.getProjectType());
                upkeepProjectRecordService.save(upkeepProjectRecord);
            }
            projectRecordList = upkeepProjectRecordService.list(new UpkeepProjectRecord() {{
                setUpkeepId(upkeepId);
            }});
        }
        map.put("projectList",projectRecordList);
        return success(map);
    }

    /**
     * 修改保养项目清单状态
     * @param recordId
     * @return
     */
    @PostMapping("/updateUpkeepProjectResult")
    @ResponseBody
    public Map<String,Object> updateUpkeepProjectResult(Long recordId){

        if(StringUtils.isNull(recordId)){
            return error(Constants.UNVERIFY,"缺少必要参数id");
        }

        UpkeepProjectRecord byId = upkeepProjectRecordService.getById(recordId);
        if(StringUtils.isNull(byId)){return error(Constants.UNVERIFY,"id参数有误！");}

        if(byId.getUpkeepResult().equals("2")){
            //未保养 -> 已保养
            byId.setUpkeepResult("1");
        }else{
            byId.setUpkeepResult("2");
        }
        return success(upkeepProjectRecordService.updateById(byId));
    }

    /**
     * 保养审核提交接口
     * @param upkeepInfo
     * @param token
     * @param type 1.维保人提交  2.审核人审核
     * @return
     */
    @PostMapping("/submitUpkeepAuditInfo")
    @ResponseBody
    @Transactional(rollbackFor = Exception.class)
    public Map<String,Object> submitUpkeepAuditInfo(UpkeepInfo upkeepInfo,String token,Integer type,String auditStatus,String scoreMark,String auditIdea) {
        if (StringUtils.isNull(upkeepInfo.getUpkeepId())) {
            return error(Constants.UNVERIFY, "缺少必要参数id");
        }
        //查询提交人
        SysUser referUser = userService.selectUserById(getUserId(token));

        UpkeepInfo byId = upkeepInfoService.getById(upkeepInfo.getUpkeepId());

        if (type == 1) {
            //签名校验
            if (StringUtils.isEmpty(upkeepInfo.getReferUserSign())) {
                return error(Constants.UNVERIFY, "请先完成签名！");
            }
            //修改保养计划最近一次保养时间
            UpkeepPlan upkeepPlans = upkeepPlanService.getByElevatorId(byId.getElevatorId());
            upkeepPlans.setRecentlyTime(String.valueOf(DateUtil.date()));
            //计算保养时长
            String datePoor = DateUtils.getDatePoor(byId.getStartTime(), DateUtil.date()).replaceAll("-","");
            upkeepInfo.setUpkeepDate(datePoor);
            //保存提交人信息
            upkeepInfo.setReferUser(referUser.getUserName());
            upkeepInfo.setReferTime(String.valueOf(DateUtil.date()));
            upkeepPlanService.updateById(upkeepPlans);

            //添加积分
            //获取上报故障积分
            String score = integralConfigService.getScoreByType(referUser.getAttrId(),"4");
            //避免输出科学计数法并去除末尾零
            referUser.setOwnScore(NumberUtil.add(referUser.getOwnScore(),score).stripTrailingZeros().toPlainString());
            userService.updateUserInfo(referUser);
            //生成积分明细
            IntegralDetail integralDetail = new IntegralDetail();
            integralDetail.setDetailTitle("电梯保养");
            integralDetail.setScoreType("0");
            integralDetail.setChangeScore("+"+score);
            integralDetail.setUserId(referUser.getUserId());
            integralDetail.setCreateBy(referUser.getUserName());
            integralDetail.setCreateTime(DateUtil.date());
            integralDetailService.save(integralDetail);

        } else if (type == 2) {
            //签名校验
            if (StringUtils.isEmpty(upkeepInfo.getAuditUserSign())) {
                return error(Constants.UNVERIFY, "请先完成签名！");
            }
            if (StringUtils.isEmpty(auditStatus)) {
                return error(Constants.UNVERIFY, "缺少审核参数！");
            }
            //保存审核人信息
            upkeepInfo.setAuditUser(referUser.getUserName());
            upkeepInfo.setAuditTime(String.valueOf(DateUtil.date()));
            //状态：改已完成 3.已保养通过
            upkeepInfo.setUpkeepState("3");
        } else {
            return error(Constants.UNVERIFY, "缺少type！");
        }

        try {
            //编辑信息
            upkeepInfoService.updateById(upkeepInfo);
            //修改保养记录 --提交给所属公司的 维保经理

            //查询维保经理
            List<SysUser> keepManagerList = userService.selectCompanyKeepManager(getUserId(token));
            UpkeepRecord upkeepRecordByKeepManager = null;
            for (SysUser keepManager : keepManagerList) {
                UpkeepRecord upkeepRecord = upkeepRecordService.selectAuditUserRecord(upkeepInfo.getUpkeepId(), keepManager.getUserId());
                if (StringUtils.isNotNull(upkeepRecord) && keepManager.getUserId().equals(getUserId(token))) {
                    upkeepRecord.setAuditStatus(auditStatus);
                    upkeepRecord.setScoreMark(scoreMark);
                    upkeepRecord.setAuditIdea(auditIdea);
                    upkeepRecord.setUpdateTime(DateUtil.date());
                    upkeepRecordService.updateById(upkeepRecord);
                } else if(StringUtils.isNull(upkeepRecord)){
                    upkeepRecordByKeepManager = new UpkeepRecord();
                    upkeepRecordByKeepManager.setUpkeepId(upkeepInfo.getUpkeepId());
                    upkeepRecordByKeepManager.setAuditUserId(keepManager.getUserId());
                    upkeepRecordByKeepManager.setAuditStatus("0");
                    upkeepRecordByKeepManager.setCreateTime(DateUtil.date());
                    upkeepRecordService.save(upkeepRecordByKeepManager);
                }
            }

        } catch (Exception e) {
            e.printStackTrace();
            return error(Constants.UNVERIFY, "服务器错误，请联系管理员!");
        }
        return success();
    }

}
